
package com.probiz.estore.webapp;

import java.net.HttpURLConnection;
import java.net.URL;
import java.util.List;
import java.util.Timer;

import javax.servlet.ServletContext;

import net.sf.ehcache.CacheManager;
import net.sf.navigator.displayer.SimpleMenuDisplayer;
import net.sf.navigator.menu.MenuComponent;
import net.sf.navigator.menu.MenuRepository;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.context.ApplicationContext;

import com.probiz.estore.Constants;
import com.probiz.estore.common.helper.ConfigUtil;
import com.probiz.estore.common.model.system.AppMenu;
import com.probiz.estore.core.util.AppContextLoader;
import com.probiz.estore.core.util.CacheUtil;
import com.probiz.estore.core.util.ContextUtil;
import com.probiz.estore.core.util.I18nUtil;
import com.probiz.estore.exception.LicenseNotFoundException;
import com.probiz.estore.system.service.AppMenuManager;
import com.probiz.estore.system.service.SystemConfigManager;
import com.probiz.estore.system.service.SystemVersionManager;
import com.probiz.estore.webapp.util.RequestContext;

public class AppContextLoaderImpl implements AppContextLoader {
	private final Log			logger	= LogFactory.getLog(AppContextLoaderImpl.class);
	private Timer				contextTimer;
	private String				licenseKey;
	private ServletContext		servletContext	= null;
	private ApplicationContext	springContext	= null;
	
	/*
	 * (non-Javadoc)
	 * @see com.probiz.estore.core.util.AppContextLoader#cleanup()
	 */
	public void cleanup() {
		if (this.contextTimer != null) {
			this.contextTimer.cancel();
			this.contextTimer = null;
		}
	}

	/*
	 * (non-Javadoc)
	 * @see com.probiz.estore.core.util.AppContextLoader#reloadContext()
	 */
	public void reloadContext() {
		logger.info("Start reloading application context...");
		checkLicense();
		reloadConfig();
		reloadMenuRepository();
		reloadLanguage();
		initEhCacheUtil();
		ContextUtil.getInstance().debugContext();
		logger.info("Reloading application context completed [OK].");
	}
	/**
	 * 检查授权
	 */
	private void checkLicense() {
		// check license
//		SystemVersionManager svm = (SystemVersionManager) springContext
//				.getBean("systemVersionManager");
//		if (svm.getSystemVersion() == null) {
//			throw new LicenseNotFoundException();
//		}
//		licenseKey = svm.getSystemVersion().getLicenseKey();
//
//		if (ContextUtil.isFront() && contextTimer == null) {
//			long __delay = 13 * 60 * 60 * 1000;
//			// long __delay = 13;
//			long __period = 57 * 60 * 60 * 1000;
//			// long __period = 300*1000;
//			contextTimer = new java.util.Timer();
//			contextTimer.schedule(new java.util.TimerTask() {
//				@Override
//				public void run() {
//					try {
//						URL url = new URL(
//								"http://www.probiz.com/onlineCheck.html?licenseKey="
//										+ licenseKey);
//						// URL url = new
//						// URL("http://192.168.16.226:8280/onlineCheck.html?licenseKey="+licenseKey);
//						HttpURLConnection connection = (HttpURLConnection) url
//								.openConnection();
//						String chReq = connection
//								.getHeaderField("probizLicense");
//						connection.disconnect();
//						SystemConfigManager confMgr = (SystemConfigManager) springContext
//								.getBean("systemConfigManager");
//						String alert = confMgr.getConfigMap().get(
//								"IsAlertLicense");
//						if ("false".equals(chReq))// Returns false. it is
//						// going to alert current
//						// system.
//						{
//							if (alert != null && alert.equals("false")) {
//								confMgr.saveConfigByKey("IsAlertLicense",
//										"true");// alert it.
//							}
//						} else // Returns true. Checking passed.
//						{
//							if (alert != null && alert.equals("true")) {
//								confMgr.saveConfigByKey("IsAlertLicense",
//										"false");// Don't alert it.
//							}
//						}
//					} catch (Exception e) {
//						// e.printStackTrace();
//						// do nothing.
//					}
//				}
//			}, __delay, __period);
//			// todo check online.
//		}

		// check license end
	}
	
	/**
	 * 初始化缓存Util
	 */
	private void initEhCacheUtil(){
		CacheUtil.getInstance().initEhCache((CacheManager) ContextUtil.getSpringBeanById(("cacheManager")));
		
	}
	
	
	/*
	 * (non-Javadoc)
	 * 
	 * @see com.probiz.estore.webapp.util.AppContextLoader#reloadConfig()
	 */
	public void reloadConfig() {
		// 从Spring acegi的bean配置读取是否允许记住我自动登录功能
// delete 直接从系统中配置		
//		try {
//			boolean rememberMeEnabled = false;
//			ProviderManager provider = (ProviderManager) springContext
//					.getBean("authenticationManager");
//			for (Iterator it = provider.getProviders().iterator(); it.hasNext();) {
//				AuthenticationProvider p = (AuthenticationProvider) it.next();
//				if (p instanceof RememberMeAuthenticationProvider) {
//					rememberMeEnabled = true;
//				}
//			}
//			ConfigUtil.getInstance().setRememberMeEnabled(rememberMeEnabled);
//		} catch (NoSuchBeanDefinitionException n) {
//			logger
//					.error(
//							"NoSuchBeanDefinitionException, ignore, should only happen when testing",
//							n);
//		}

		ConfigUtil.getInstance().checkConfigAtStartup();
		servletContext.setAttribute(Constants.CONFIG, ConfigUtil.getInstance());

		logger.debug("Config reloaded [OK].");
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see com.probiz.estore.webapp.util.AppContextLoader#reloadLanguage()
	 */
	@Deprecated
	public void reloadLanguage() {
		// set system default language
		try {
			Constants.SYSTEM_LOCALE_CODE = ConfigUtil.getInstance().getSystemLocaleCode();
			I18nUtil.initDefaultLocale();
			I18nUtil.initAllSupportedLocale(new String[] { "zh_CN", "en" });
		} catch (Exception e) {
			throw new RuntimeException("No supported language, or default system language not set, or unexpected system error!!!", e);
		}
		logger.debug("Language reloaded [OK].");
	}

	/*
	 * (non-Javadoc)
	 * @see com.probiz.estore.core.util.AppContextLoader#reloadMenuRepository()
	 */
	public void reloadMenuRepository() {
		if (logger.isDebugEnabled()) {
			logger.debug("Starting struts-menu initialization");
		}

		try {

			/**************************原menu-config菜单实现start********************/
//			String menuConfig = "/WEB-INF/classes/conf/menu-config.xml";
//			MenuRepository repository = new MenuRepository();
//			repository.setLoadParam(menuConfig);
//			repository.setServletContext(servletContext);
//			repository.load();
//			servletContext.setAttribute(MenuRepository.MENU_REPOSITORY_KEY,	repository);
//			servletContext.setAttribute(Constants.KEY_MENU_CONTEXT,	repository.getTopMenus());
			/**************************原menu-config菜单实现end********************/
			
			/**************************数据库菜单实现start********************/
			AppMenuManager appMenuManager = (AppMenuManager) springContext.getBean("appMenuManager");
			List<AppMenu> menus = appMenuManager.findAllMenus(RequestContext.getSecurityBelongTo(),Constants.SECURITY_TYPE_MENU);
			MenuRepository menuRepository = new MenuRepository();
			menuRepository.getDisplayers().put("Simple",new SimpleMenuDisplayer());
			for(AppMenu m:menus){
				if(m.getParent()==null){
					MenuComponent mc = new MenuComponent();
					mc.setName(m.getMenuName());
					mc.setTitle(m.getTitle());
					mc.setPage(m.getUrl());
					menuRepository.addMenu(mc);
				}
			}
			for(AppMenu m:menus){
				if(m.getParent()!=null){
					if(m.getParent().getParent()==null){//第二层
						MenuComponent pmc = menuRepository.getMenu(m.getParent().getMenuName());
						if(pmc==null)
							continue;
						MenuComponent mc = new MenuComponent();
						mc.setName(m.getMenuName());
						mc.setTitle(m.getTitle());
						mc.setPage(m.getUrl());
						pmc.getComponents().add(mc);
						mc.setParent(pmc);
					}
				}
			}
			
			if(!RequestContext.isFront()){//后台需要3层处理
				for(AppMenu m:menus){
					if(m.getParent()!=null){
						if(m.getParent().getParent()!=null){//第三层
							MenuComponent pmc1 = menuRepository.getMenu(m.getParent().getParent().getMenuName());
							MenuComponent mc = new MenuComponent();
							mc.setName(m.getMenuName());
							mc.setTitle(m.getTitle());
							mc.setPage(m.getUrl());
							for(int i=0;i<pmc1.getComponents().size();i++){
								MenuComponent pmc2=(MenuComponent)pmc1.getComponents().get(i);
								if(pmc2.getName().equals(m.getParent().getMenuName())){
									pmc2.getComponents().add(mc);
									mc.setParent(pmc2);
									break;
								}
							}
						}
					}
				}
			}
//			MenuRepository menuRepository = getMenuRepository();
			servletContext.setAttribute(MenuRepository.MENU_REPOSITORY_KEY,	menuRepository);
			servletContext.setAttribute(Constants.KEY_MENU_CONTEXT,	menuRepository.getTopMenus());
			/**************************数据库菜单实现end********************/
			if (logger.isDebugEnabled()) {
				logger.debug("Struts-menu initialization [OK].");
			}
		} catch (Exception lre) {
			lre.printStackTrace();
			logger.fatal("Failure initializing Struts-menu: "+ lre.getMessage());
		}
	}
//	/**
//	 * 获得菜单资源库
//	 * @return
//	 * @deprecated
//	 */
//	private MenuRepository getMenuRepository(){
//		MenuRepository  menuRepository = new MenuRepository();
//		AppMenuManager appMenuManager = (AppMenuManager) springContext.getBean("appMenuManager");
//		List<AppMenu> topMenuList = appMenuManager.findTopMenus(RequestContext.getSecurityBelongTo(),Constants.SECURITY_TYPE_MENU);
//		for(AppMenu menu : topMenuList){
//			addMenuComponent(menuRepository,menu);
//		}
//		menuRepository.getDisplayers().put("Simple",new SimpleMenuDisplayer());
//		return menuRepository;
//	}
//	/**
//	 * 使用迭代递归方法填充菜单资源库
//	 * 优点：代码优美，易读，扩展性好，无限级菜单不需更新代码
//	 * 缺点：需要多次读取数据库，达到100多条
//	 * @param parent 父级component或repository
//	 * @param menu 要增加到子集合的menu
//	 * @deprecated
//	 */
//	private void addMenuComponent(Object parent, AppMenu menu){
//		AppMenuManager appMenuManager = (AppMenuManager) springContext.getBean("appMenuManager");
//		MenuComponent menuComponent = new MenuComponent();
//		menuComponent.setName(menu.getMenuName());
//		menuComponent.setTitle(menu.getTitle());
//		menuComponent.setPage(menu.getUrl());
//		if(parent instanceof MenuRepository){
//			MenuRepository parentRepository = (MenuRepository)parent;
//			parentRepository.addMenu(menuComponent);
//		}else{
//			MenuComponent parentComponent = (MenuComponent)parent;
//			parentComponent.getComponents().add(menuComponent);
//			menuComponent.setParent(parentComponent);
//		}
//		List<AppMenu> children = (List<AppMenu>)appMenuManager.findChildrenByMenuId(menu.getMenuId());
//		if(children.size() > 0){
//			for(AppMenu child : children){
//				addMenuComponent(menuComponent, child);
//			}
//		}
//	}


	public void setServletContext(ServletContext servletContext) {
		this.servletContext = servletContext;
	}

	public void setSpringContext(ApplicationContext springContext) {
		this.springContext = springContext;
	}

}
